/**
 * 智慧水务设备通信模块
 * 
 * @version 1.0.0
 * @date 2024-03-xx
 * 
 * 版本历史：
 * 1.0.0 - 初始版本
 * - 实现基础数据和高级数据显示
 * - 实现蓝牙通信功能
 * - 实现 Modbus 协议解析
 * 
 * 1.0.1 - 修复时间显示
 * - 修改时间显示逻辑
 * - UTC时间和北京时间显示在基础数据最后
 * - 修复时间格式为 YYYY.MM.DD.HH.MM.SS
 */

// 添加权限配置
const AUTH_LEVELS = {
  NORMAL: 0,    // 普通用户
  MAINTAIN: 1,  // 运维人员
  ADVANCED: 2,  // 高级用户
  DEVELOPER: 3  // 开发人员
}

/*
基础数据点表 - 只读参考（按显示顺序排列）
地址 : 名称
------------------------
0    : 水位 (cm)
1    : 压力水位 (cm)
61   : 雷达强度
6    : 瞬时值 (cm)
2    : 电池电压 (V)
4    : 信号强度 (dBm)
7    : 信噪比 (dB)
5    : 温度 (°C)
82   : 探头温度 (°C)
101  : 探头湿度 (%)
110  : 保存条数
111  : 上传条数
28-42: IMEI号码        // 特殊处理 - 15位数字
72-76: SIM卡号         // 特殊处理 - 20位数字
113  : 设备版本
104-109: UTC时间       // 特殊处理 - YYYY.MM.DD.HH.MM.SS
104-109: 北京时间      // 特殊处理 - YYYY.MM.DD.HH.MM.SS

注意事项：
1. 顺序不可更改
2. 名称和单位不可更改
3. 特殊处理的数据（IMEI、SIM、时间）需要按照指定格式显示
4. 时间始终显示在最后
*/

/*
高级数据点表 - 只读参考（按显示顺序排列）
地址 : 名称
------------------------
3    : 剩余电量
23   : 采集间隔 (秒)
24   : 上传间隔 (秒)
25   : 休眠时间 (秒)
26   : 唤醒时间 (秒)
88   : 设备地址
57   : 波特率
58   : 数据位
56   : 校验位
89-92: IP地址1         // 特殊处理 - 点分十进制格式 (xxx.xxx.xxx.xxx)
18   : 端口号
64   : 电池校准斜率K
65   : 电池校准斜率A
66   : 压力校准斜率K
67   : 压力校准斜率A
68   : 压力校准确认
69   : 超声波探头类型
70   : 压力探头类型

// 未命名的地址放在最后
62   : 触发类型
71   : 电源类型
77   : 预警数据频率
78   : 告警数据频率
80   : 压力零点切换值
81   : 传感器波特率
83   : 超声波校准温度
84   : 超声波校准确认
85   : 温度自动变化率
86   : 压力校准值
87   : 压力校准确认
93   : RTC时钟参数
112  : 硬件版本
*/

// 添加寄存器配置
const REGISTER_CONFIG = {
  // 基础数据地址列表
  basicAddresses: [
    0,    // 水位
    1,    // 压力
    2,    // 电池电压
    4,    // 信号强度
    5,    // 温度
    6,    // 水位变化率
    7,    // 信噪比
    82,   // 探头温度
    101,  // 探头湿度
    112,  // 硬件版本
    113,  // 软件版本
  ],

  // 高级数据地址列表 - 按功能分类
  advancedAddresses: [
    // 超声波相关
    57,   // 超声波探头类型
    83,   // 超声波校准温度
    84,   // 超声波校准值
    85,   // 超声波校准确认
    64,   // 阻尼系数
    65,   // 限幅幅度
    86,   // 温度自动变化率
    // 压力相关
    58,   // 压力探头类型
    25,   // 压力校准斜率K
    26,   // 压力校准偏置A
    80,   // 压力零点切换值
    87,   // 压力校准值
    88,   // 压力确认校准
    81,   // 传感器波特率
    // 数据采集相关
    62,   // 触发类型
    56,   // 正常数据频率
    77,   // 预警数据频率
    78,   // 告警数据频率
    // 电池相关
    71,   // 电源类型
    23,   // 电池校准斜率K
    24,   // 电池校准偏置A
    70,   // 电池使用电量
    3,    // 剩余电量
    69,   // 电池效率
    // 系统参数
    93,   // RTC时钟参数
    89,   // IP地址1
    90,   // IP地址2
    91,   // IP地址3
    92,   // IP地址4
    18,   // 端口号
    8,    // 初始化（仅高级人员可见）
  ],

  // 可写入地址列表
  writableAddresses: [
    89, 90, 91, 92,  // IP地址
    18,   // 端口号
    93,   // RTC时钟参数
    3,    // 剩余电量
    8,    // 初始化
    64, 65, 66, 67, 68,  // 校准相关
    69, 70,              // 探头类型
    23, 24,              // 频率设置
    25, 26,              // 休眠和唤醒时间
    57, 58, 56,          // 波特率、数据位、校验位
    88,                  // 设备地址
    62, 71, 77, 78,      // 触发类型等
    80, 81, 83, 84, 85, 86, 87  // 其他可修改参数
  ],

  // 特殊显示配置
  specialDisplays: {
    imei: { 
      start: 28, 
      end: 42,
      format: 'imei',
      label: 'IMEI号码',
      combine: true  // 标记需要组合显示
    },
    simCard: { 
      start: 72, 
      end: 76,
      format: 'simCard',
      label: 'SIM卡号',
      combine: true  // 标记需要组合显示
    },
    time: {
      start: 104,
      end: 109,
      format: 'time',
      showUTC: true,  // 显示UTC时间
      showBeijing: true,  // 显示北京时间
      label: {
        utc: 'UTC时间',
        beijing: '北京时间'
      }
    },
    ip: { 
      start: 89, 
      end: 92,
      label: 'IP地址1',
      format: 'ip',
      writable: true
    }
  }
}

// 添加地址名称映射
const REGISTER_NAMES = {
  0: '水位 (cm)',
  1: '压力 (cm)',
  2: '电池电压 (V)',
  4: '信号强度 (dBm)',
  5: '温度 (°C)',
  6: '水位变化率 (cm)',
  7: '信噪比 (dB)',
  8: '初始化',
  82: '探头温度 (°C)',
  101: '探头湿度 (%)',
  112: '硬件版本',
  113: '软件版本',
  28: 'IMEI号码',
  72: 'SIM卡号',
  113: '设备版本',
  104: 'UTC时间',
  105: '北京时间',
  3: '剩余电量',
  23: '采集间隔 (秒)',
  24: '上传间隔 (秒)',
  25: '休眠时间 (秒)',
  26: '唤醒时间 (秒)',
  88: '设备地址',
  57: '超声波探头类型',
  58: '压力探头类型',
  25: '压力校准斜率K',
  26: '压力校准偏置A',
  80: '压力零点切换值',
  87: '压力校准值',
  88: '压力确认校准',
  81: '传感器波特率',
  62: '触发类型',
  56: '正常数据频率',
  77: '预警数据频率',
  78: '告警数据频率',
  71: '电源类型',
  23: '电池校准斜率K',
  24: '电池校准偏置A',
  70: '电池使用电量',
  3: '剩余电量',
  69: '电池效率',
  93: 'RTC时钟参数',
  89: 'IP地址1',
  90: 'IP地址2',
  91: 'IP地址3',
  92: 'IP地址4',
  18: '端口号',
  112: '硬件版本',
  83: '超声波校准温度',
  84: '超声波校准值',
  85: '超声波校准确认',
  64: '阻尼系数',
  65: '限幅幅度',
  86: '温度自动变化率'
}

// 添加下拉选择配置
const SELECT_OPTIONS = {
  17: {  // 通信运营商
    type: 'select',
    options: [
      { value: '0', label: '电信' },
      { value: '1', label: '移动' },
      { value: '2', label: '联通' },
      { value: '3', label: '广电' }
    ]
  },
  43: {  // 计量模式
    type: 'select',
    options: [
      { value: '0', label: '空距模式' },
      { value: '1', label: '水深模式' }
    ]
  },
  47: {  // 通信方式
    type: 'select',
    options: [
      { value: '0', label: '4G' },
      { value: '1', label: 'NB' }
    ]
  },
  57: {  // 超声波探头类型
    type: 'select',
    options: [
      { value: '0', label: '不使用' },
      { value: '1', label: '雷达探头' },
      { value: '7', label: '超声波探头' }
    ],
    mode: 'selector'  // 使用选择器模式
  },
  58: {  // 压力探头类型
    type: 'select',
    options: [
      { value: '0', label: '4-20mA压力' },
      { value: '1', label: 'RS485压力' },
      { value: '2', label: '小型水尺' },
      { value: '3', label: '麦克485压力' }
    ],
    mode: 'selector'  // 使用选择器模式
  },
  62: {  // 触发报警模式
    type: 'select',
    options: [
      { value: '0', label: '不触发' },
      { value: '1', label: '触发1次' },
      { value: '2', label: '连续触发' }
    ]
  },
  22: {  // 485波特率
    type: 'select',
    options: [
      { value: '0', label: '1200' },
      { value: '1', label: '9600' },
      { value: '2', label: '57600' },
      { value: '3', label: '115200' }
    ]
  },
  79: {  // 超声波电压
    type: 'select',
    options: [
      { value: '0', label: '7V' },
      { value: '1', label: '9V' },
      { value: '2', label: '12V' },
      { value: '3', label: '14V' }
    ]
  },
  19: {  // RTC时间模式
    type: 'select',
    options: [
      { value: '0', label: '主芯片' },
      { value: '1', label: '外部RTC' }
    ]
  },
  20: {  // 禁止休眠模式
    type: 'select',
    options: [
      { value: '0', label: '允许休眠' },
      { value: '1', label: '禁止休眠' }
    ]
  },
  46: {  // 485模式
    type: 'select',
    options: [
      { value: '0', label: '主机' },
      { value: '1', label: '从机' }
    ]
  },
  51: {  // AT指令切换
    type: 'select',
    options: [
      { value: '0', label: '关闭' },
      { value: '1', label: '开启' }
    ]
  },
  55: {  // 投入2路485
    type: 'select',
    options: [
      { value: '0', label: '关闭' },
      { value: '1', label: '开启' }
    ]
  },
  71: {  // 电源自动校准
    type: 'select',
    options: [
      { value: '0', label: '正常模式' },
      { value: '1', label: 'AT指令模式' },
      { value: '2', label: '恢复正常模式' }
    ]
  },
  67: {  // 盲区值
    type: 'select',
    options: [
      { value: '0', label: 'GPRS' },
      { value: '1', label: 'NB-IoT' },
      { value: '2', label: 'ELTE' }
    ]
  },
  72: {  // 供电方式
    type: 'select',
    options: [
      { value: '0', label: '内部电池供电' },
      { value: '1', label: '外部供电' }
    ]
  },
  81: {  // 传感器波特率
    type: 'select',
    options: [
      { value: '1', label: '9600' },
      { value: '0', label: '115200' }
    ],
    mode: 'selector'  // 使用选择器模式
  },
  71: {  // 电源类型
    type: 'select',
    options: [
      { value: '0', label: '电池供电' },
      { value: '1', label: '外接电源' }
    ],
    mode: 'selector'  // 使用选择器模式
  },
  62: {  // 触发类型
    type: 'select',
    options: [
      { value: '0', label: '正常模式' },
      { value: '1', label: '触发一次' },
      { value: '2', label: '连续触发' }
    ],
    mode: 'selector'  // 使用选择器模式
  }
}

// 添加按键模式配置
const BUTTON_OPTIONS = {
  9: {    // 休眠
    type: 'button',
    label: '休眠',
    value: '1'
  },
  16: {   // 设备开关
    type: 'button',
    label: '关机',
    confirmText: '确认进行关机操作吗？',
    value: '1'
  },
  10: {   // 重启
    type: 'button',
    label: '重启',
    value: '1'
  },
  114: {  // 清空保存数据
    type: 'button',
    label: '清空数据',
    value: '1'
  }
}

// 添加特殊按钮配置
const BUTTON_CONFIG = {
   85: {  // 超声波校准确认
     type: 'confirm',
     label: '确认校准',
     value: 1,
     confirmText: '确认要校准吗？'
   },
   88: {  // 压力确认校准
     type: 'confirm',
     label: '确认校准',
     value: 1,
     confirmText: '确认要压力校准吗？'
   }
}

// 添加默认值配置
const DEFAULT_VALUES = {
   8: '3856'  // 初始化的默认值
}

Page({
  data: {
    deviceId: '',
    deviceInfo: {},
    serviceId: '',
    writeCharacteristicId: '',
    readCharacteristicId: '',
    connected: false,
    basicRegisters: [],
    advancedRegisters: [],
    showAdvancedSection: false,
    isNotifying: false,
    queryTimer: null,
    rssiTimer: null,
    txCount: 0,
    rxCount: 0,
    receivedDataText: '',
    buttonLeft: 20,
    buttonTop: 300,
    isLogExpanded: false,
    authLevel: 0,
    receivedBuffer: [],  // 添加接收缓冲区
    isReceiving: false,  // 是否正在接收数据
    expectedLength: 0,   // 期望的数据长度
  },

  onLoad(options) {
    const { deviceId } = options
    const authLevel = wx.getStorageSync('authLevel') || 0
    
    // 初始化基础数据点表
    const basicRegisters = [
      { addr: 0, name: '水位', unit: 'cm' },
      { addr: 1, name: '压力水位', unit: 'cm' },
      { addr: 2, name: '电池电压', unit: 'V' },
      { addr: 3, name: '剩余电量', unit: '%' },
      { addr: 4, name: '信号强度', unit: 'dBm' },
      { addr: 7, name: '信噪比', unit: 'dB' },
      { addr: 5, name: '温度', unit: '°C' },
      { addr: 6, name: '瞬时值', unit: 'cm' },
      { addr: 61, name: '雷达强度', unit: '' },
      { addr: 82, name: '探头温度', unit: '°C' },
      { addr: 101, name: '探头湿度', unit: '%' },
      { addr: 110, name: '保存条数', unit: '' },
      { addr: 111, name: '上传条数', unit: '' },
      { addr: 113, name: '设备版本', unit: '' },
      { addr: '28-42', name: 'IMEI号码', type: 'string', length: 15 },
      { addr: '72-76', name: 'SIM卡号', type: 'string', length: 20 },
      { addr: '104-109', name: 'UTC时间', type: 'time', length: 6 },
      { addr: '104-109', name: '北京时间', type: 'time', length: 6 }
    ].map(register => ({
      ...register,
      value: '--'  // 初始值显示为--
    }))
    
    this.setData({
      deviceId,
      authLevel,
      basicRegisters,
      showAdvancedSection: authLevel >= 1,  // 运维及以上权限显示高级数据
      deviceInfo: {
        name: '',
        RSSI: '',
        connected: false
      }
    })
    
    // 获取设备名称和信号强度
    wx.getBLEDeviceRSSI({
      deviceId: deviceId,
      success: (res) => {
        this.setData({
          'deviceInfo.RSSI': res.RSSI
        })
      }
    })

    wx.getBluetoothDevices({
      success: (res) => {
        const device = res.devices.find(d => d.deviceId === deviceId)
        if (device) {
          this.setData({
            'deviceInfo.name': device.name || '未知设备'
          })
        }
      }
    })
    
    // 添加蓝牙数据变化监听
    wx.onBLECharacteristicValueChange((result) => {
      if (result.characteristicId.toUpperCase().includes('FFF1')) {
        const receivedData = new Uint8Array(result.value)
        console.log('收到原始数据:', this.ab2hex(result.value))
        this.parseModbusResponse(receivedData)
        // 更新接收计数
        this.setData({
          rxCount: this.data.rxCount + 1
        })
      }
    })
    
    this.connectDevice()
  },

  onUnload() {
    // 页面卸载时确保清理所有资源
    if (this.queryTimer) {
      clearInterval(this.queryTimer)
      this.queryTimer = null
    }
    if (this.rssiTimer) {
      clearInterval(this.rssiTimer)
      this.rssiTimer = null
    }

    // 如果还在通知状态，先关闭通知
    if (this.data.isNotifying) {
      wx.notifyBLECharacteristicValueChange({
        deviceId: this.data.deviceId,
        serviceId: this.data.serviceId,
        characteristicId: this.data.readCharacteristicId,
        state: false
      })
    }

    // 确保关闭连接
    wx.closeBLEConnection({
      deviceId: this.data.deviceId,
      complete: () => {
        setTimeout(() => {
          wx.closeBluetoothAdapter()
        }, 200)
      }
    })

    // 清理接收缓冲区和状态标志
    this.receivedBuffer = []
    this.isReceiving = false
    this.expectedLength = 0
    this.lastPacketTime = 0
  },

  getDeviceName() {
    wx.getBluetoothDevices({
      success: (result) => {
        const device = result.devices.find(d => d.deviceId === this.data.deviceId)
        if (device) {
          this.setData({
            'deviceInfo.name': device.name || '未知设备'
          })
        }
      }
    })
  },

  getDeviceInfo() {
    wx.getBLEDeviceRSSI({
      deviceId: this.data.deviceId,
      success: (res) => {
        this.setData({
          'deviceInfo.RSSI': res.RSSI
        })
      }
    })
  },

  connectToFFF0Service() {
    // 添加超时处理
    const timeout = setTimeout(() => {
      console.log('获取服务超时')
      this.reconnectDevice()
    }, 5000)

    wx.getBLEDeviceServices({
      deviceId: this.data.deviceId,
      success: (res) => {
        clearTimeout(timeout)
        console.log('所有服务列表:', res.services)
        
        // 查找 FFF0 服务
        const targetService = res.services.find(service => {
          const uuid = service.uuid.toUpperCase()
          return uuid === '0000FFF0-0000-1000-8000-00805F9B34FB' || 
                 uuid === '0000FFF0' ||
                 uuid.includes('FFF0')
        })
        
        if (targetService) {
          console.log('找到 FFF0 服务:', targetService.uuid)
          this.getBLEDeviceCharacteristics(targetService.uuid)
        } else {
          console.error('未找到 FFF0 服务')
          this.reconnectDevice()
        }
      },
      fail: (err) => {
        clearTimeout(timeout)
        console.error('获取服务失败:', err)
        this.reconnectDevice()
      }
    })
  },

  getBLEDeviceCharacteristics(serviceId) {
    wx.getBLEDeviceCharacteristics({
      deviceId: this.data.deviceId,
      serviceId: serviceId,
      success: (res) => {
        console.log('特征值列表:', res.characteristics)
        
        // 查找写入和读取特征值
        const writeChar = res.characteristics.find(c => 
          c.uuid.toUpperCase().includes('FFF2')
        )
        const readChar = res.characteristics.find(c => 
          c.uuid.toUpperCase().includes('FFF1')
        )

        if (writeChar && readChar) {
          console.log('找到写入特征值:', writeChar.uuid)
          console.log('找到读取特征值:', readChar.uuid)
          
          this.setData({
            serviceId: serviceId,
            writeCharacteristicId: writeChar.uuid,
            readCharacteristicId: readChar.uuid
          })

          // 启用读取特征值的通知
          this.startNotify(readChar.uuid)
        } else {
          console.error('未找到所需特征值')
        }
      },
      fail: (err) => {
        console.error('获取特征值失败:', err)
      }
    })
  },

  startNotify(characteristicId) {
    wx.notifyBLECharacteristicValueChange({
      deviceId: this.data.deviceId,
      serviceId: this.data.serviceId,
      characteristicId: characteristicId,
      state: true,
      success: () => {
        console.log('启用通知成功')
        this.setData({ isNotifying: true })
        
        // 延迟启动查询
        setTimeout(() => {
          this.startQueryTimer()
        }, 500)
      },
      fail: (err) => {
        console.error('启用通知失败:', err)
        this.reconnectDevice()
      }
    })
  },

  sendModbusQuery() {
    if (this.data.isReceiving) {
      console.log('上一次查询还未完成，跳过本次查询')
      return
    }

    if (!this.data.serviceId || !this.data.writeCharacteristicId) {
      console.log('蓝牙特征值未就绪')
      this.stopQueryTimer()
      return
    }

    const buffer = new ArrayBuffer(8)
    const view = new DataView(buffer)
    
    // Modbus RTU 查询帧格式:
    // 从站地址(1字节) + 功能码(1字节) + 起始地址(2字节) + 寄存器数量(2字节) + CRC(2字节)
    view.setUint8(0, 0x02)  // 从站地址 02
    view.setUint8(1, 0x03)  // 功能码 03（读保持寄存器）
    view.setUint16(2, 0x0000, false)  // 起始地址 0000
    view.setUint16(4, 0x0078, false)  // 寄存器数量 120个 (0x78 = 120)

    const crc = this.calculateModbusCRC(new Uint8Array(buffer.slice(0, 6)))
    view.setUint8(6, crc & 0xFF)
    view.setUint8(7, (crc >> 8) & 0xFF)

    // 保存查询参数，用于验证响应
    this.queryParams = {
      slaveAddr: 0x02,
      functionCode: 0x03,
      startAddr: 0x0000,
      registerCount: 0x0078
    }

    // 打印发送的查询指令
    console.log('发送查询指令:', this.ab2hex(buffer))

    wx.writeBLECharacteristicValue({
      deviceId: this.data.deviceId,
      serviceId: this.data.serviceId,
      characteristicId: this.data.writeCharacteristicId,
      value: buffer,
      success: () => {
        console.log('查询发送成功')
        this.setData({
          txCount: this.data.txCount + 1
        })
      },
      fail: (err) => {
        console.error('查询发送失败:', err)
        this.stopQueryTimer()
        setTimeout(() => {
          this.startQueryTimer()
        }, 5000)
      }
    })
  },

  calculateModbusCRC(data) {
    let crc = 0xFFFF
    for (let i = 0; i < data.length; i++) {
      crc ^= data[i]
      for (let j = 0; j < 8; j++) {
        if (crc & 0x0001) {
          crc = (crc >> 1) ^ 0xA001
        } else {
          crc >>= 1
        }
      }
    }
    return crc
  },

  ab2hex(buffer) {
    return Array.prototype.map.call(
      new Uint8Array(buffer),
      bit => ('00' + bit.toString(16)).slice(-2)
    ).join('')
  },

  disconnectDevice() {
    // 显示加载提示
    wx.showLoading({
      title: '正在断开连接',
      mask: true
    })

    // 先停止所有查询和通知
    this.stopQueryTimer()
    if (this.data.isNotifying) {
      wx.notifyBLECharacteristicValueChange({
        deviceId: this.data.deviceId,
        serviceId: this.data.serviceId,
        characteristicId: this.data.readCharacteristicId,
        state: false,
        complete: () => {
          this.closeConnection()
        }
      })
    } else {
      this.closeConnection()
    }
  },

  // 关闭连接
  closeConnection() {
    // 先停止所有定时器和通知
    this.stopQueryTimer()
    if (this.data.isNotifying) {
      wx.notifyBLECharacteristicValueChange({
        deviceId: this.data.deviceId,
        serviceId: this.data.serviceId,
        characteristicId: this.data.readCharacteristicId,
        state: false
      })
    }

    // 清理所有状态
    this.setData({
      isNotifying: false,
      serviceId: '',
      writeCharacteristicId: '',
      readCharacteristicId: ''
    })

    wx.closeBLEConnection({
      deviceId: this.data.deviceId,
      complete: () => {
        // 隐藏加载提示
        wx.hideLoading()

        // 先关闭蓝牙适配器
        wx.closeBluetoothAdapter({
          complete: () => {
            // 返回上一页
            wx.navigateBack({
              complete: () => {
                // 确保完全退出后再重置蓝牙
                setTimeout(() => {
                  // 重新初始化蓝牙适配器
                  wx.openBluetoothAdapter({
                    fail: (err) => {
                      console.error('蓝牙初始化失败:', err)
                    }
                  })
                }, 2000)  // 延长等待时间到2秒
              }
            })
          }
        })
      }
    })
  },

  // 修改数据包验证逻辑
  parseModbusPacket(packet) {
    // 忽略单字节的无效数据包
    if (packet.length <= 1) {
      console.log('忽略无效数据包:', this.ab2hex(packet))
      return
    }

    // 验证从站地址和功能码
    if (packet[0] !== 0x02 || packet[1] !== 0x03) {
      console.log('数据包格式错误:', this.ab2hex(packet))
      return
    }
    
    // 获取数据长度
    const dataLength = packet[2]
    const totalLength = 3 + dataLength + 2  // 头部(3) + 数据 + CRC(2)
    
    // 检查数据包完整性
    if (packet.length !== totalLength) {  // 修改这里，使用严格相等
      console.log('数据包长度不符，期望:', totalLength, '实际:', packet.length)
      return
    }

    // 验证CRC
    const calculatedCRC = this.calculateModbusCRC(packet.slice(0, dataLength + 3))
    const receivedCRC = (packet[dataLength + 4] << 8) | packet[dataLength + 3]
    
    if (calculatedCRC !== receivedCRC) {
      console.log('CRC校验失败，计算值:', calculatedCRC.toString(16), '接收值:', receivedCRC.toString(16))
      return
    }

    // 提取有效数据
    const data = packet.slice(3, 3 + dataLength)
    return data
  },

  // 修改数据解析函数
  parseModbusResponse(packet) {
    const data = this.parseModbusPacket(packet)
    if (!data) return

    // 调试输出
    console.log('收到数据包长度:', data.length)
    console.log('数据内容:', this.ab2hex(data))

    // 更新接收计数
    this.setData({
      rxCount: this.data.rxCount + 1
    })

    // 更新基础数据点表
    const basicRegisters = this.data.basicRegisters.map(register => {
      // 处理特殊地址范围
      if (typeof register.addr === 'string' && register.addr.includes('-')) {
        return this.parseSpecialRegister(register, data)
      }
      
      // 处理普通地址
      const addr = parseInt(register.addr)
      if (addr >= 0 && addr < 120) {  // 确保地址在有效范围内
        const value = data[addr]
        return {
          ...register,
          value: this.formatValue(value, register.unit)
        }
      }
      return register
    })

    this.setData({ basicRegisters })
  },

  // 判断是否为基础数据（后续根据提供的地址列表修改）
  isBasicRegister(addr) {
    // 处理特殊显示的地址
    for (const key in REGISTER_CONFIG.specialDisplays) {
      const range = REGISTER_CONFIG.specialDisplays[key]
      if (addr.includes('-')) {
        // 处理合并显示的地址，如 "28-42"
        const startAddr = addr.split('-')[0]
        return REGISTER_CONFIG.basicAddresses.includes(parseInt(startAddr))
      }
    }
    // 处理普通地址
    return REGISTER_CONFIG.basicAddresses.includes(parseInt(addr))
  },

  // 判断是否有权限查看某个地址的数据
  hasPermission(addr) {
    // 处理组合地址（如 IP 地址 "89-92"）
    if (addr.includes('-')) {
      const [start, end] = addr.split('-').map(Number)
      if (start === 89 && end === 92) {
        return this.data.authLevel >= AUTH_LEVELS.ADVANCED
      }
      return false
    }

    const address = parseInt(addr)
    // 地址 8 仅高级人员可见
    if (address === 8) {
      return this.data.authLevel >= AUTH_LEVELS.ADVANCED
    }
    // IP地址和端口号仅高级用户及以上可修改
    if (address >= 89 && address <= 92 || address === 18) {
      return this.data.authLevel >= AUTH_LEVELS.ADVANCED
    }
    // 调试模式按钮仅开发人员可见
    if (address === 'debug_mode') {
      return this.data.authLevel === AUTH_LEVELS.DEVELOPER
    }
    // 其他地址的权限判断保持不变
    return true
  },

  // 判断是否为可写入数据
  isWritableRegister(addr) {
    // 处理 IP 地址的特殊情况
    if (addr.includes('-')) {
      const [start, end] = addr.split('-').map(Number)
      if (start === 89 && end === 92) {
        // IP地址需要高级权限
        return this.data.authLevel >= AUTH_LEVELS.ADVANCED
      }
      return false
    }
    
    // 先检查权限
    if (!this.hasPermission(addr)) return false
    
    return REGISTER_CONFIG.writableAddresses.includes(parseInt(addr))
  },

  // 修改编辑功能
  showEditModal(e) {
    // 阻止事件冒泡
    e && e.stopPropagation && e.stopPropagation()
    
    const register = e.currentTarget.dataset.register
    if (!register.writable) return

    // 处理 IP 地址特殊情况
    if (register.isIpAddress || register.addr === '89-92') {
      wx.showModal({
        title: '修改IP地址',
        placeholderText: '请输入完整IP地址',
        content: register.value || '',
        editable: true,
        success: (res) => {
          if (res.confirm && res.content) {
            // 验证 IP 地址格式
            const ipPattern = /^(\d{1,3}\.){3}\d{1,3}$/
            if (!ipPattern.test(res.content)) {
              wx.showToast({
                title: 'IP格式错误',
                icon: 'none'
              })
              return
            }
            
            // 拆分 IP 地址并写入
            const ipParts = res.content.split('.')
            let hasError = false
            for (let i = 0; i < 4; i++) {
              const value = parseInt(ipParts[i])
              if (value < 0 || value > 255) {
                wx.showToast({
                  title: 'IP范围错误',
                  icon: 'none'
                })
                hasError = true
                break
              }
            }
            
            if (!hasError) {
              // 依次写入四个 IP 地址段
              for (let i = 0; i < 4; i++) {
                const addr = 89 + i  // IP地址从89开始，到92结束
                const value = parseInt(ipParts[i])
                this.updateRegisterValue(addr, value)
              }
              
              // 更新显示
              const newAdvancedRegisters = [...this.data.advancedRegisters]
              const ipIndex = newAdvancedRegisters.findIndex(r => r.isIpAddress)
              if (ipIndex >= 0) {
                newAdvancedRegisters[ipIndex].value = res.content
                this.setData({
                  advancedRegisters: newAdvancedRegisters
                })
              }
            }
          }
        }
      })
      return
    }

    const selectConfig = SELECT_OPTIONS[parseInt(register.addr)]
    const buttonConfig = BUTTON_OPTIONS[parseInt(register.addr)]
    
    if (buttonConfig) {
      // 按键模式直接写入值
      wx.showModal({
        title: '确认',
        content: buttonConfig.confirmText || `确定要${buttonConfig.label}吗？`,
        success: (res) => {
          if (res.confirm) {
            this.updateRegisterValue(register.addr, buttonConfig.value)
          }
        }
      })
    } else if (selectConfig) {
      // 使用下拉选择
      wx.showActionSheet({
        itemList: selectConfig.options.map(opt => opt.label),
        success: (res) => {
          if (res.tapIndex >= 0) {
            const selectedValue = selectConfig.options[res.tapIndex].value
            this.updateRegisterValue(register.addr, selectedValue)
          }
        }
      })
    } else {
      // 使用普通输入框
      wx.showModal({
        title: '修改数据',
        placeholderText: '请输入新的值',
        editable: true,
        success: (res) => {
          if (res.confirm) {
            // 验证输入是否为数字
            if (!res.content) {
              wx.showToast({
                title: '请输入数值',
                icon: 'none'
              })
              return
            }
            
            // 检查是否只包含数字
            if (!/^\d+$/.test(res.content)) {
              wx.showToast({
                title: '请输入纯数字',
                icon: 'none'
              })
              return
            }
            
            // 检查数值范围（可选，根据需要设置）
            const value = parseInt(res.content)
            if (value < 0 || value > 65535) {
              wx.showToast({
                title: '数值超出范围',
                icon: 'none'
              })
              return
            }
            
            this.updateRegisterValue(register.addr, res.content)
          }
        }
      })
    }
  },

  // 更新寄存器值
  updateRegisterValue(addr, value) {
    if (!this.data.serviceId || !this.data.writeCharacteristicId) return

    // 创建 Modbus RTU 06 写入指令
    const buffer = new ArrayBuffer(8)
    const view = new DataView(buffer)
    
    view.setUint8(0, 0x02)  // 从站地址 02
    view.setUint8(1, 0x06)  // 功能码 06（写单个寄存器）
    view.setUint16(2, parseInt(addr), false)  // 寄存器地址
    view.setUint16(4, parseInt(value), false)  // 写入值

    // 计算 CRC
    const crc = this.calculateModbusCRC(new Uint8Array(buffer.slice(0, 6)))
    view.setUint8(6, crc & 0xFF)
    view.setUint8(7, (crc >> 8) & 0xFF)

    const hexString = this.ab2hex(buffer)
    console.log('发送写入数据:', hexString)
    this.addLog('send', hexString)  // 记录发送的数据

    // 发送写入指令
    wx.writeBLECharacteristicValue({
      deviceId: this.data.deviceId,
      serviceId: this.data.serviceId,
      characteristicId: this.data.writeCharacteristicId,
      value: buffer,
      success: () => {
        console.log('写入成功')
        this.setData({
          txCount: this.data.txCount + 1
        })
        // 写入成功后显示提示
        wx.showToast({
          title: '写入成功',
          icon: 'success',
          duration: 2000
        })
      },
      fail: (err) => {
        console.error('写入失败:', err)
        // 写入失败时显示错误提示
        wx.showToast({
          title: '写入失败',
          icon: 'error',
          duration: 2000
        })
      }
    })
  },

  // 更新寄存器名称映射
  getRegisterName(addr) {
    const registerNames = {
      0: '水位 (cm)',
      1: '压力 (cm)',
      2: '电池电压 (V)',
      4: '信号强度 (dBm)',
      5: '温度 (°C)',
      6: '水位变化率 (cm)',
      7: '信噪比 (dB)',
      8: '初始化',
      82: '探头温度 (°C)',
      101: '探头湿度 (%)',
      112: '硬件版本',
      113: '软件版本',
      28: 'IMEI号码',
      72: 'SIM卡号',
      113: '设备版本',
      104: 'UTC时间',
      105: '北京时间',
      3: '剩余电量',
      23: '采集间隔 (秒)',
      24: '上传间隔 (秒)',
      25: '休眠时间 (秒)',
      26: '唤醒时间 (秒)',
      88: '设备地址',
      57: '超声波探头类型',
      58: '压力探头类型',
      25: '压力校准斜率K',
      26: '压力校准偏置A',
      80: '压力零点切换值',
      87: '压力校准值',
      88: '压力确认校准',
      81: '传感器波特率',
      62: '触发类型',
      56: '正常数据频率',
      77: '预警数据频率',
      78: '告警数据频率',
      71: '电源类型',
      23: '电池校准斜率K',
      24: '电池校准偏置A',
      70: '电池使用电量',
      3: '剩余电量',
      69: '电池效率',
      93: 'RTC时钟参数',
      89: 'IP地址1',
      90: 'IP地址2',
      91: 'IP地址3',
      92: 'IP地址4',
      18: '端口号',
      112: '硬件版本',
      83: '超声波校准温度',
      84: '超声波校准值',
      85: '超声波校准确认',
      64: '阻尼系数',
      65: '限幅幅度',
      86: '温度自动变化率'
    }
    return registerNames[addr] || `寄存器${addr}`
  },

  // 添加触摸开始事件处理
  buttonTouchStart(e) {
    this.startX = e.touches[0].clientX
    this.startY = e.touches[0].clientY
    this.buttonLeft = this.data.buttonLeft
    this.buttonTop = this.data.buttonTop
  },

  // 添加触摸移动事件处理
  buttonTouchMove(e) {
    const moveX = e.touches[0].clientX - this.startX
    const moveY = e.touches[0].clientY - this.startY
    
    // 计算新位置
    let newLeft = this.buttonLeft + moveX
    let newTop = this.buttonTop + moveY
    
    // 获取屏幕尺寸
    const systemInfo = wx.getSystemInfoSync()
    
    // 防止按钮超出屏幕边界
    newLeft = Math.max(0, Math.min(newLeft, systemInfo.windowWidth - 100))
    newTop = Math.max(0, Math.min(newTop, systemInfo.windowHeight - 100))
    
    this.setData({
      buttonLeft: newLeft,
      buttonTop: newTop
    })
  },

  addLog(type, data) {
    const timestamp = new Date().toLocaleTimeString()
    const prefix = type === 'send' ? 'T' : type === 'receive' ? 'R' : 'S'
    const newLog = `${timestamp} ${prefix}: ${data}`
    
    const updatedData = [...this.data.receivedData, newLog]
    this.setData({
      receivedData: updatedData,
      receivedDataText: updatedData.join('\n')
    })
  },

  toggleLog() {
    this.setData({
      isLogExpanded: !this.data.isLogExpanded
    })
  },

  // 检查权限
  checkAuth() {
    // 这里可以从本地存储或服务器获取权限状态
    const authLevel = wx.getStorageSync('authLevel') || AUTH_LEVELS.NONE
    this.setData({ 
      authLevel,
      showAdvancedSection: authLevel > AUTH_LEVELS.NONE
    })
  },

  // 获取用户权限
  getUserAuth() {
    // 开发调试时直接使用运维权限
    if (__wxConfig.platform === 'devtools' || true) {  // true 表示真机也使用调试权限
      this.setData({
        authLevel: AUTH_LEVELS.MAINTAIN,
        showAdvancedSection: true
      })
      if (this.lastResponse) {
        this.parseModbusResponse(this.lastResponse)
      }
      return
    }

    // 以下是正式环境的权限验证逻辑
    const cachedAuth = wx.getStorageSync('authLevel')
    const authExpireTime = wx.getStorageSync('authExpireTime')
    
    if (cachedAuth && authExpireTime && Date.now() < authExpireTime) {
      // 缓存未过期，使用缓存的权限
      this.setData({
        authLevel: cachedAuth,
        showAdvancedSection: cachedAuth > AUTH_LEVELS.NONE
      })
      if (this.lastResponse) {
        this.parseModbusResponse(this.lastResponse)
      }
      return
    }

    // 缓存过期或不存在，重新获取权限
    wx.login({
      success: (res) => {
        if (res.code) {
          this.checkUserAuthLevel(res.code)
        }
      }
    })
  },

  // 检查用户权限等级
  checkUserAuthLevel(code) {
    // 调用后台接口获取用户权限等级
    wx.request({
      url: 'YOUR_BACKEND_API/check-auth',  // 替换为实际的后台接口
      data: {
        code: code
      },
      success: (res) => {
        if (res.data.success) {
          const authLevel = res.data.authLevel
          this.setData({ 
            authLevel,
            showAdvancedSection: authLevel > AUTH_LEVELS.NONE
          })
          // 存储权限信息
          wx.setStorageSync('authLevel', authLevel)
          // 重新解析数据以更新显示
          if (this.lastResponse) {
            this.parseModbusResponse(this.lastResponse)
          }
        }
      },
      fail: (err) => {
        console.error('获取权限失败:', err)
        // 权限验证失败时使用最低权限
        this.setData({
          authLevel: AUTH_LEVELS.NONE,
          showAdvancedSection: false
        })
      }
    })
  },

  // 添加一个函数来获取选项的标签
  getSelectOptionLabel(addr, value) {
    const selectConfig = SELECT_OPTIONS[addr]
    if (!selectConfig) return value

    const option = selectConfig.options.find(opt => opt.value === value)
    return option ? option.label : value
  },

  // 添加一个函数来格式化特定地址的值
  formatRegisterValue(addr, value) {
    // 转换为数字
    const numValue = parseInt(value)
    
    // 信号强度和信噪比需要处理成有符号数
    if ([4, 7].includes(addr)) {
      return numValue > 32767 ? (numValue - 65536).toString() : numValue.toString()
    }
    
    // 电池电压 (V) - 除以100，保留2位小数
    if (addr === 2) {
      return (numValue / 100).toFixed(2)
    }
    
    // 温度 (°C) 和探头温度 (°C) - 除以10，保留1位小数
    if (addr === 5 || addr === 82) {
      return (numValue / 10).toFixed(1)
    }
    
    // 探头湿度 (%) - 直接显示原始值
    if (addr === 101) {
      return numValue.toString()
    }
    
    // 传感器波特率特殊处理
    if (addr === 81) {
      const config = SELECT_OPTIONS[81]
      const option = config.options.find(opt => opt.value === value.toString())
      return option ? option.label : value
    }
    
    // 电源类型特殊处理
    if (addr === 71) {
      const config = SELECT_OPTIONS[71]
      const option = config.options.find(opt => opt.value === value.toString())
      return option ? option.label : value
    }
    
    // 探头类型特殊处理
    if (addr === 57 || addr === 58) {
      const config = SELECT_OPTIONS[addr]
      const option = config.options.find(opt => opt.value === value.toString())
      return option ? option.label : value
    }
    
    return value
  },

  // 添加 IP 地址的特殊处理函数
  formatIPAddress(registers) {
    const ip = []
    for (let i = 89; i <= 92; i++) {
      const reg = registers.find(r => parseInt(r.addr) === i)
      if (reg && reg.value !== undefined) {
        ip.push(reg.value)
      }
    }
    // 只有当收集到4个有效的IP段时才返回
    return ip.length === 4 ? ip.join('.') : ''
  },

  // 添加时间值格式化函数
  formatTimeValue(value) {
    const num = parseInt(value)
    return num < 10 ? `0${num}` : `${num}`
  },

  // 修改蓝牙数据接收处理
  onBLECharacteristicValueChange(result) {
    if (result.characteristicId.toUpperCase().includes('FFF1')) {
      const receivedData = new Uint8Array(result.value)
      console.log('收到原始数据:', this.ab2hex(result.value))

      const currentTime = Date.now()
      // 如果距离上一个包的时间超过100ms，认为是新的数据包开始
      if (currentTime - this.lastPacketTime > 100) {
        this.receivedBuffer = []
        this.isReceiving = false
        this.expectedLength = 0
      }
      this.lastPacketTime = currentTime

      // 如果是新的数据包开始（以0x02 0x03开头）
      if (receivedData[0] === 0x02 && receivedData[1] === 0x03) {
        this.receivedBuffer = Array.from(receivedData)
        this.isReceiving = true
        if (receivedData.length >= 3) {
          const dataLength = receivedData[2]
          this.expectedLength = 3 + dataLength + 2  // 头部(3) + 数据 + CRC(2)
        }
      } 
      // 如果正在接收数据，则追加到缓冲区
      else if (this.isReceiving) {
        this.receivedBuffer = [...this.receivedBuffer, ...Array.from(receivedData)]
      }

      // 如果已经接收到足够的数据
      if (this.isReceiving && this.receivedBuffer.length >= this.expectedLength) {
        // 解析完整的数据包
        this.parseModbusResponse(new Uint8Array(this.receivedBuffer))
        
        // 更新接收计数
        this.setData({
          rxCount: this.data.rxCount + 1
        })
        
        // 重置接收状态
        this.receivedBuffer = []
        this.isReceiving = false
        this.expectedLength = 0
      }
    }
  },

  // 添加数据包验证函数
  validatePacket(packet) {
    if (packet.length < 5) return false
    if (packet[0] !== 0x02) return false
    if (packet[1] !== 0x03) return false
    const dataLength = packet[2]
    if (packet.length !== dataLength + 5) return false
    
    // 验证CRC
    const calculatedCRC = this.calculateModbusCRC(packet.slice(0, dataLength + 3))
    const receivedCRC = (packet[dataLength + 4] << 8) | packet[dataLength + 3]
    return calculatedCRC === receivedCRC
  },

  // 解析完整的数据包
  parseCompletePacket(packet) {
    console.log('开始解析数据包:', this.ab2hex(packet))
    // 检查数据包格式
    if (packet[0] !== 0x02 || packet[1] !== 0x03) {
      console.log('数据包格式错误: 头部不匹配', packet[0], packet[1])
      return
    }
    
    // 获取数据长度
    const dataLength = packet[2]
    console.log('数据长度:', dataLength, '包总长度:', packet.length)
    if (packet.length < dataLength + 5) {  // 包括头部3字节和CRC 2字节
      console.log('数据包长度不足，期望:', dataLength + 5, '实际:', packet.length)
      return
    }
    
    // 验证CRC
    const calculatedCRC = this.calculateModbusCRC(packet.slice(0, dataLength + 3))
    const receivedCRC = (packet[dataLength + 4] << 8) | packet[dataLength + 3]
    
    if (calculatedCRC !== receivedCRC) {
      console.log('CRC校验失败，计算值:', calculatedCRC.toString(16), '接收值:', receivedCRC.toString(16))
      return
    }
    
    console.log('数据包验证通过，开始解析数据')
    // 解析数据
    this.parseModbusResponse(packet)
  },

  // 添加定时查询功能
  startQueryTimer() {
    if (this.queryTimer) {
      clearInterval(this.queryTimer)
    }
    
    // 先立即执行一次查询和更新
    this.sendModbusQuery()
    this.getDeviceInfo()  // <-- 添加这行
    
    this.queryTimer = setInterval(() => {
      this.sendModbusQuery()
      this.getDeviceInfo()  // <-- 添加这行
    }, 1000)
  },

  stopQueryTimer() {
    if (this.queryTimer) {
      clearInterval(this.queryTimer)
      this.queryTimer = null
    }
  },

  onShow() {
    this.startQueryTimer()
  },

  onHide() {
    this.stopQueryTimer()
  },

  onUnload() {
    this.stopQueryTimer()
    // 断开蓝牙连接
    this.disconnectDevice()
    // 清理接收缓冲区和状态标志
    this.receivedBuffer = []
    this.isReceiving = false
    this.expectedLength = 0
    this.lastPacketTime = 0
  },

  // 添加重连逻辑
  reconnectDevice() {
    console.log('开始重连设备')
    // 先停止所有查询
    this.stopQueryTimer()
    
    wx.closeBLEConnection({
      deviceId: this.data.deviceId,
      complete: () => {
        // 清理状态
        this.setData({
          serviceId: '',
          writeCharacteristicId: '',
          readCharacteristicId: '',
          isNotifying: false,
          'deviceInfo.connected': false
        })
        
        setTimeout(() => {
          this.connectDevice()  // 重新尝试连接
        }, 1000)
      }
    })
  },

  // 修改组合显示处理函数
  formatCombinedValue(registers, start, end) {
    const values = []
    for (let i = start; i <= end; i++) {
      const reg = registers.find(r => parseInt(r.addr) === i)
      if (reg && reg.value !== undefined) {
        if (start === 28 && end === 42) {  // IMEI 码
          // 直接使用原始值
          values.push(reg.value.toString())
        } else if (start === 72 && end === 76) {  // SIM 卡号
          // 转换为16进制并补足4位
          const hexValue = parseInt(reg.value).toString(16).padStart(4, '0')
          values.push(hexValue)
        }
      }
    }

    if (start === 28 && end === 42) {
      return values.join('')  // IMEI 码
    }
    if (start === 72 && end === 76) {
      return values.join('').toUpperCase()  // SIM 卡号转大写
    }
    return values.join('')
  },

  // 添加高级数据判断函数
  isAdvancedRegister(addr) {
    return REGISTER_CONFIG.advancedAddresses.includes(parseInt(addr))
  },

  // 添加判断是否为特殊显示寄存器的函数
  isSpecialDisplayRegister(addr) {
    for (const key in REGISTER_CONFIG.specialDisplays) {
      const config = REGISTER_CONFIG.specialDisplays[key]
      if (addr >= config.start && addr <= config.end) {
        return true
      }
    }
    return false
  },

  // 添加确认按钮处理函数
  handleConfirmButton(e) {
    const register = e.currentTarget.dataset.register
    const config = BUTTON_CONFIG[register.addr]
    
    if (!config) return
    
    wx.showModal({
      title: '提示',
      content: config.confirmText,
      success: (res) => {
        if (res.confirm) {
          // 写入值 1
          this.writeRegisterValue(register.addr, config.value)
          wx.showToast({
            title: '已确认校准',
            icon: 'success'
          })
        }
      }
    })
  },

  // 写入寄存器值
  writeRegisterValue(addr, value) {
    // 构建 Modbus 写入命令
    const buffer = new ArrayBuffer(11)
    const view = new DataView(buffer)
    
    view.setUint8(0, 0x02)  // 从站地址
    view.setUint8(1, 0x06)  // 功能码 06（写单个寄存器）
    view.setUint16(2, parseInt(addr), false)  // 寄存器地址
    view.setUint16(4, value, false)  // 写入值
    
    const crc = this.calculateModbusCRC(new Uint8Array(buffer.slice(0, 6)))
    view.setUint8(6, crc & 0xFF)
    view.setUint8(7, (crc >> 8) & 0xFF)

    wx.writeBLECharacteristicValue({
      deviceId: this.data.deviceId,
      serviceId: this.data.serviceId,
      characteristicId: this.data.writeCharacteristicId,
      value: buffer,
      success: () => {
        console.log('写入成功')
        wx.showToast({
          title: '写入成功',
          icon: 'success',
          duration: 1500
        })
      },
      fail: (err) => {
        console.error('写入失败:', err)
        wx.showToast({
          title: '写入失败',
          icon: 'error',
          duration: 1500
        })
      }
    })
  },

  // 添加选择器处理函数
  showSelectModal(e) {
    const register = e.currentTarget.dataset.register
    const config = SELECT_OPTIONS[register.addr]
    
    if (!config || !config.options) return
    
    wx.showActionSheet({
      itemList: config.options.map(opt => opt.label),
      success: (res) => {
        if (res.tapIndex >= 0) {
          const selectedOption = config.options[res.tapIndex]
          this.writeRegisterValue(register.addr, parseInt(selectedOption.value))
        }
      }
    })
  },

  // 修改 showEditModal 函数
  showEditModal(e) {
    const register = e.currentTarget.dataset.register
    const defaultValue = DEFAULT_VALUES[register.addr] || register.value
    
    wx.showModal({
      title: '修改数值',
      editable: true,
      content: defaultValue,
      placeholderText: '请输入新的数值',
      success: (res) => {
        if (res.confirm) {
          const newValue = parseInt(res.content)
          if (!isNaN(newValue)) {
            this.writeRegisterValue(register.addr, newValue)
          }
        }
      }
    })
  },

  // 修改 IP 地址写入函数
  writeIPAddress(ipString) {
    const ipParts = ipString.split('.')
    if (ipParts.length !== 4) {
      wx.showToast({
        title: 'IP格式错误',
        icon: 'error',
        duration: 1500
      })
      return
    }
    
    // 逐个写入IP地址段
    for (let i = 0; i < 4; i++) {
      const addr = 89 + i
      const value = parseInt(ipParts[i])
      if (!isNaN(value) && value >= 0 && value <= 255) {
        this.writeRegisterValue(addr, value)
      } else {
        wx.showToast({
          title: 'IP段格式错误',
          icon: 'error',
          duration: 1500
        })
        return
      }
    }
    wx.showToast({
      title: 'IP写入成功',
      icon: 'success',
      duration: 1500
    })
  },

  // 添加 IP 地址修改对话框
  showIPEditModal(e) {
    const register = e.currentTarget.dataset.register
    const currentIP = register.value || '0.0.0.0'
    const ipParts = currentIP.split('.')
    
    wx.showModal({
      title: '修改IP地址',
      content: `当前IP: ${currentIP}`,
      editable: true,
      placeholderText: '请输入新IP (xxx.xxx.xxx.xxx)',
      success: (res) => {
        if (res.confirm) {
          const newIP = res.content
          if (/^(\d{1,3}\.){3}\d{1,3}$/.test(newIP)) {
            this.writeIPAddress(newIP)
          } else {
            wx.showToast({
              title: 'IP格式错误',
              icon: 'none'
            })
          }
        }
      }
    })
  },

  // 修改蓝牙页面的初始化逻辑
  initBluetooth() {
    // 先关闭蓝牙适配器
    wx.closeBluetoothAdapter({
      complete: () => {
        // 延迟后重新打开蓝牙适配器
        setTimeout(() => {
          wx.openBluetoothAdapter({
            success: (res) => {
              console.log('蓝牙初始化成功')
              this.startBluetoothDevicesDiscovery()
            },
            fail: (res) => {
              wx.showToast({
                title: '请打开蓝牙',
                icon: 'none'
              })
            }
          })
        }, 1000)  // 等待1秒后重新初始化
      }
    })
  },

  // 解析时间寄存器
  parseTimeRegister(data, startAddr, length) {
    const bytes = []
    for(let i = 0; i < length; i++) {
      bytes.push(data[startAddr + i])
    }
    
    // 解析时间格式 
    const year = bytes[0] * 256 + bytes[1]
    const month = bytes[2]
    const day = bytes[3]
    const hour = bytes[4] 
    const minute = bytes[5]
    const second = bytes[6] || 0

    // 格式化为 YYYY.MM.DD.HH.MM.SS
    return `${year}.${this.pad(month)}.${this.pad(day)}.${this.pad(hour)}.${this.pad(minute)}.${this.pad(second)}`
  },

  // 数字补零
  pad(num) {
    return num < 10 ? '0' + num : num
  },

  // 格式化数值
  formatValue(value, unit) {
    if (value === undefined || value === null) {
      return '--'
    }

    // 处理特殊单位的转换
    switch (unit) {
      case 'V':
        return (value / 100).toFixed(2) // 电压值需要除以100
      case 'dBm':
        return value - 256 // 信号强度需要减256
      case '°C':
        return (value / 10).toFixed(1) // 温度值需要除以10
      case '%':
        return value // 百分比直接显示
      case 'cm':
        return value // 厘米直接显示
      case 'dB':
        return value // 分贝直接显示
      default:
        return value // 其他情况直接返回原值
    }
  },

  // 修改 parseSpecialRegister 函数
  parseSpecialRegister(register, data) {
    const { addr, type, length } = register
    
    if(type === 'time') {
      // 解析地址范围,如 "104-109"
      const [start] = addr.split('-').map(Number)
      return {
        ...register,
        value: this.parseTimeRegister(data, start, length)
      }
    }
    
    if(type === 'string') {
      // 解析字符串类型...
      const [start] = addr.split('-').map(Number) 
      return {
        ...register,
        value: this.parseStringRegister(data, start, length)
      }
    }

    return register
  },

  // 添加字符串解析函数
  parseStringRegister(data, startAddr, length) {
    const bytes = []
    for(let i = 0; i < length; i++) {
      bytes.push(data[startAddr + i])
    }
    return bytes.map(b => String.fromCharCode(b)).join('')
  },

  // 修改连接设备函数
  connectDevice() {
    wx.getBLEDeviceServices({
      deviceId: this.data.deviceId,
      success: () => {
        console.log('设备已连接，直接获取服务')
        this.setData({
          'deviceInfo.connected': true
        })
        // 连接成功后应该更新设备名称和信号强度
        this.getDeviceName()  // <-- 添加这行
        this.getDeviceInfo()  // <-- 添加这行
        this.getDeviceServices()
      },
      fail: () => {
        // 设备未连接，尝试建立连接
        wx.createBLEConnection({
          deviceId: this.data.deviceId,
          success: () => {
            console.log('设备连接成功')
            this.setData({
              'deviceInfo.connected': true  // 更新连接状态
            })
            // 获取服务
            this.getDeviceServices()
          },
          fail: (err) => {
            console.error('设备连接失败:', err)
            this.setData({
              'deviceInfo.connected': false  // 更新连接状态
            })
            wx.showToast({
              title: '连接失败',
              icon: 'none'
            })
          }
        })
      }
    })
  },

  // 获取设备服务
  getDeviceServices() {
    // 添加延时，等待连接稳定
    setTimeout(() => {
      wx.getBLEDeviceServices({
        deviceId: this.data.deviceId,
        success: (res) => {
          const services = res.services
          // 查找 FFF0 服务
          const fff0Service = services.find(s => 
            s.uuid.toUpperCase().includes('FFF0')
          )
          
          if (fff0Service) {
            this.setData({
              serviceId: fff0Service.uuid
            })
            // 获取特征值
            this.getDeviceCharacteristics()
          } else {
            console.error('未找到 FFF0 服务')
            this.reconnectDevice()
          }
        },
        fail: (err) => {
          console.error('获取服务失败:', err)
          this.reconnectDevice()
        }
      })
    }, 1000)  // 延时1秒
  },

  // 获取特征值
  getDeviceCharacteristics() {
    wx.getBLEDeviceCharacteristics({
      deviceId: this.data.deviceId,
      serviceId: this.data.serviceId,
      success: (res) => {
        const characteristics = res.characteristics
        
        // 查找写入和读取特征值
        characteristics.forEach(char => {
          const uuid = char.uuid.toUpperCase()
          if (uuid.includes('FFF1')) {
            this.setData({
              readCharacteristicId: char.uuid
            })
            // 启用通知
            this.enableNotify()
          } else if (uuid.includes('FFF2')) {
            this.setData({
              writeCharacteristicId: char.uuid
            })
          }
        })
        
        // 开始定时查询
        this.startQueryTimer()
      },
      fail: (err) => {
        console.error('获取特征值失败:', err)
      }
    })
  },

  // 启用通知
  enableNotify() {
    wx.notifyBLECharacteristicValueChange({
      deviceId: this.data.deviceId,
      serviceId: this.data.serviceId,
      characteristicId: this.data.readCharacteristicId,
      state: true,
      success: () => {
        console.log('通知启用成功')
        this.setData({
          isNotifying: true
        })
      },
      fail: (err) => {
        console.error('启用通知失败:', err)
      }
    })
  }
})          